package com.qys.livesMall.shop.scheduledTask.task;

import com.qys.livesMall.app.user.model.entity.H2AppUser;
import com.qys.livesMall.app.user.model.entity.H2AppUserRechargeWithdrawals;
import com.qys.livesMall.app.user.model.entity.SysOperateReport;
import com.qys.livesMall.app.user.service.IH2AppUserRechargeWithdrawalsService;
import com.qys.livesMall.app.user.service.IH2AppUserService;
import com.qys.livesMall.app.user.service.SysOperateReportService;
import com.qys.livesMall.app.user.service.UserStatisticsDayLogService;
import com.qys.livesMall.common.utils.DateUtils;
import com.qys.livesMall.finance.enums.AccountBusinessTypeEnum;
import com.qys.livesMall.finance.mapper.FinanceShopAccountDetailMapper;
import com.qys.livesMall.finance.mapper.FinanceUserAccountDetailMapper;
import com.qys.livesMall.finance.model.entity.shop.FinanceShopAccountDetail;
import com.qys.livesMall.finance.model.entity.user.FinanceUserAccountDetail;
import com.qys.livesMall.shop.mapper.H2ShopRechargeWithdrawalMapper;
import com.qys.livesMall.shop.modal.entity.H2ShopRechargeWithdrawal;
import com.qys.livesMall.shop.modal.entity.ShopStatisticsEveryDay;
import com.qys.livesMall.shop.service.ShopStatisticsEverydayService;
import jakarta.annotation.Resource;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import java.math.BigDecimal;
import java.util.Date;
import java.util.List;

/**
 * 运营报表
 */
@Component
public class SysOperateReportScheduledTask {
    @Resource
    private SysOperateReportService sysOperateReportService;
    @Resource
    private IH2AppUserRechargeWithdrawalsService userRechargeService;
    @Resource
    private IH2AppUserService ih2AppUserService;
    @Resource
    private FinanceUserAccountDetailMapper userAccountDetailMapper;
    @Resource
    private H2ShopRechargeWithdrawalMapper rechargeWithdrawalMapper;
    @Resource
    private FinanceShopAccountDetailMapper financeShopAccountDetailMapper;
    @Resource
    private UserStatisticsDayLogService userStatisticsDayLogService;
    @Resource
    private ShopStatisticsEverydayService shopStatisticsEverydayService;

    @Scheduled(cron = "0 0 3 * * ?") // 每天晚上3点执行一次
    public void operateReportInfoTask() {
        //i=0 真实用户-用户
        //i=1 虚拟用户-用户
        //i=2 真是用户-店铺
        //i=3 虚拟用户-店铺
        for (int i = 0; i < 4; i++) {
            SysOperateReport operateReport= new SysOperateReport();
            Date date= DateUtils.yesterday();
            operateReport.setDate(DateUtils.format(date,"yyyy-MM-dd"));
            Integer userSysType=i % 2 == 0 ? 1 :0;
            operateReport.setUserSysType(userSysType);
            Integer type=i >=2 ? 1 : 0;
            operateReport.setType(type);
            operateReport.setRecharge(BigDecimal.ZERO);
            operateReport.setFirstCharge(BigDecimal.ZERO);
            operateReport.setWithdrawal(BigDecimal.ZERO);
            operateReport.setActualAmount(BigDecimal.ZERO);
            operateReport.setGiveWinnings(BigDecimal.ZERO);
            operateReport.setTeamCommission(BigDecimal.ZERO);
            if (type == 0){
                List<H2AppUser> h2AppUsers=ih2AppUserService.getYesterday();
                if (CollectionUtils.isNotEmpty(h2AppUsers)){
                    Long registerNum=h2AppUsers.stream().filter(a->a.getUserSysType()==1 || a.getUserSysType()==2).count();
                    operateReport.setRechargeNum(null==registerNum?0:registerNum.intValue());
                }else {
                    Long registerNum=h2AppUsers.stream().filter(a->a.getUserSysType()==0).count();
                    operateReport.setRechargeNum(null==registerNum?0:registerNum.intValue());
                }
                userConvert(operateReport,userSysType);
            }else {
                shopConvert(operateReport,userSysType);
            }
            sysOperateReportService.save(operateReport);
        }
    }

    public void userConvert(SysOperateReport operateReport,Integer userSysType){
        //用户充值提现明细
        List<H2AppUserRechargeWithdrawals> userRW = userRechargeService.getYesterdayRwDate(userSysType);
        if (CollectionUtils.isNotEmpty(userRW)){
            //充值金额
            BigDecimal recharge=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode())) .map(H2AppUserRechargeWithdrawals::getRealAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setRecharge(recharge);
            //充值人数
            Long rechargeNum=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode())).map(H2AppUserRechargeWithdrawals::getUserId).distinct().count();
            operateReport.setRechargeNum(null==rechargeNum?0:rechargeNum.intValue());
            //首充金额
            BigDecimal firstCharge=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode()) && a.getNum()==1) .map(H2AppUserRechargeWithdrawals::getRealAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setFirstCharge(firstCharge);
            //首充人数
            Long firstChargeNum=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode()) && a.getNum()==1).map(H2AppUserRechargeWithdrawals::getUserId).distinct().count();
            operateReport.setFirstChargeNum(null==firstChargeNum?0:firstChargeNum.intValue());
            //提现金额
            BigDecimal withdrawal=userRW.stream().filter(a->a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2AppUserRechargeWithdrawals::getAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setWithdrawal(withdrawal);
            //出款金额
            BigDecimal actualAmount=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2AppUserRechargeWithdrawals::getRealAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setActualAmount(actualAmount);
            //提现人数
            Long withdrawalNum=userRW.stream().filter(a->1 == (int)a.getAuditType() && a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2AppUserRechargeWithdrawals::getRealAmount).distinct().count();
            operateReport.setWithdrawalNum(null==withdrawalNum?0:withdrawalNum.intValue());
        }
        List<FinanceUserAccountDetail> financeUserAccountDetails = userAccountDetailMapper.getYesterday(userSysType);
        if (CollectionUtils.isNotEmpty(financeUserAccountDetails)){
            //赠送礼金
            BigDecimal giveWinnings=financeUserAccountDetails.stream().filter(a->AccountBusinessTypeEnum.GIFT.getCode().equals(a.getCode())).map(FinanceUserAccountDetail::getAmountIncurred).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setGiveWinnings(giveWinnings);
            //团队佣金
            BigDecimal teamCommission =financeUserAccountDetails.stream().filter(a->AccountBusinessTypeEnum.getUserCommissionCode().contains(a.getCode())).map(FinanceUserAccountDetail::getAmountIncurred).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setTeamCommission(teamCommission);
            //用户收益
            BigDecimal revenueAmount= financeUserAccountDetails.stream().filter(a->AccountBusinessTypeEnum.getUserIncomeCode().contains(a.getCode())).map(FinanceUserAccountDetail::getAmountIncurred).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setRevenueAmount(revenueAmount);
        }
    }

    public void shopConvert(SysOperateReport operateReport,Integer userSysType){
        //店铺充值提现明细
        List<H2ShopRechargeWithdrawal> shopRW=rechargeWithdrawalMapper.getYesterdayRwDate(userSysType);
        if (CollectionUtils.isNotEmpty(shopRW)){
            //充值金额
            BigDecimal recharge=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode())) .map(H2ShopRechargeWithdrawal::getActualArrivalAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setRecharge(recharge.add(operateReport.getRecharge()));
            //充值人数
            Long rechargeNum=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode())).map(H2ShopRechargeWithdrawal::getUserId).distinct().count();
            operateReport.setRechargeNum(rechargeNum.intValue());
/*            //首充金额
            BigDecimal firstCharge=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode()) && a.getNum()==1) .map(H2ShopRechargeWithdrawal::getActualArrivalAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setFirstCharge(firstCharge);
            //首充人数
            Long firstChargeNum=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.RECHARGE.getCode()) && a.getNum()==1).map(H2ShopRechargeWithdrawal::getUserId).distinct().count();
            operateReport.setFirstChargeNum(firstChargeNum);*/
            //提现金额
            BigDecimal withdrawal=shopRW.stream().filter(a->a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2ShopRechargeWithdrawal::getAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setWithdrawal(withdrawal.add(operateReport.getWithdrawal()));
            //出款金额
            BigDecimal actualAmount=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2ShopRechargeWithdrawal::getActualArrivalAmount).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setActualAmount(actualAmount);
            //提现人数
            Long withdrawalNum=shopRW.stream().filter(a->a.getStatus().equals("1") && a.getType().equals(AccountBusinessTypeEnum.WITHDRAWAL.getCode())).map(H2ShopRechargeWithdrawal::getActualArrivalAmount).distinct().count();
            operateReport.setWithdrawalNum(withdrawalNum.intValue());
        }
        List<FinanceShopAccountDetail> financeShopAccountDetails = financeShopAccountDetailMapper.getYesterday(userSysType);
        if (CollectionUtils.isNotEmpty(financeShopAccountDetails)){
            BigDecimal giveWinnings=financeShopAccountDetails.stream().filter(a->AccountBusinessTypeEnum.GIFT.getCode().equals(a.getCode())).map(FinanceShopAccountDetail::getAmountIncurred).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setGiveWinnings(giveWinnings);
            BigDecimal teamCommission =financeShopAccountDetails.stream().filter(a->AccountBusinessTypeEnum.getShopCommissionCode().contains(a.getCode())).map(FinanceShopAccountDetail::getAmountIncurred).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setTeamCommission(teamCommission);
        }
        List<ShopStatisticsEveryDay> shopStatisticsEveryDays=shopStatisticsEverydayService.getYesterday(userSysType);
        if (CollectionUtils.isNotEmpty(shopStatisticsEveryDays)){
            BigDecimal revenueAmount= shopStatisticsEveryDays.stream().map(ShopStatisticsEveryDay::getIncome).reduce(BigDecimal.ZERO,BigDecimal::add);
            operateReport.setRevenueAmount(revenueAmount.add(operateReport.getRevenueAmount()));
        }
    }
}
